#ifndef JSINGLETON_H
#define JSINGLETON_H

#include <QtCore/qmutex.h>

#ifndef J_MUTEX_LOCKER
# define J_MUTEX_LOCKER(mutexType, _mutex, ...) \
	std::unique_lock<mutexType> __mutex_locker__##__VA_ARGS__(_mutex); \
	Q_UNUSED(__mutex_locker__##__VA_ARGS__)
#endif

#ifndef J_STD_MUTEX_LOCKER
# define J_STD_MUTEX_LOCKER(_mutex, ...) \
	J_MUTEX_LOCKER(std::mutex, _mutex, __VA_ARGS__)
#endif

#ifndef J_QMUTEX_LOCKER
# define J_QMUTEX_LOCKER(_mutex, ...) \
	QMutexLocker __mutex_locker__##__VA_ARGS__(&_mutex); \
	Q_UNUSED(__mutex_locker__##__VA_ARGS__)
#endif

#ifndef J_MUTEX_LOCKER_RELOCK
# define J_MUTEX_LOCKER_RELOCK(...) \
	__mutex_locker__##__VA_ARGS__.lock()
#endif

#ifndef J_MUTEX_LOCKER_UNLOCK
# define J_MUTEX_LOCKER_UNLOCK(...) \
	__mutex_locker__##__VA_ARGS__.unlock()
#endif

/*------------------------------------------------------------------------------------------*/

// 永久的单例（C++11静态变量定义是原子的）
#define J_PERMANENT_SINGLETON(Class) \
	public: \
		static Class &instance() \
		{ \
			static Class __unique_object__; \
			return __unique_object__; \
		} \
	private: \
		Class(); \
		~Class() {} \
		Q_DISABLE_COPY(Class)

// 可销毁的单例
#define J_VOLATILE_SINGLETON(Class) \
	public: \
		static Class *unique_object; \
		static std::mutex unique_object_lock; \
		static Class &instance() \
		{ \
			if( unique_object == nullptr ) \
			{ \
				J_MUTEX_LOCKER(std::mutex, unique_object_lock); \
				if( unique_object == nullptr ) \
					unique_object = new Class(); \
			} \
			return *unique_object; \
		} \
		void destroyInstance() \
		{ \
			if( unique_object != nullptr ) \
			{ \
				static std::mutex __delete_lock__; \
				J_MUTEX_LOCKER(std::mutex, __delete_lock__) \
				if( unique_object != nullptr ) \
				{ \
					delete unique_object; \
					unique_object = nullptr; \
				} \
			} \
		} \
	private: \
		Class(); \
		~Class(); \
		Q_DISABLE_COPY(Class)

#define J_VOLATILE_SINGLETON_OBJECT(Class) \
	Class *Class::unique_object = nullptr; \
	std::mutex Class::unique_object_lock;


#endif //JSINGLETON_H
